angular.module('starter.services', [])

	.constant('ApiEndpoint', {
		//url : "../../",
		//settingUrl : 'http://10.100.235.94:8080/rs/ad/v1/2',
		//codesUrl : 'http://10.100.235.94:8080/rs/ad/v1/3',
		//queryNameUrl : 'http://10.100.235.94:8080/rs/ad/v1/4',
		//queryUserUrl : 'http://10.100.235.94:8080/rs/ad/v1/5',
		//queryBusOrStopUrl : 'http://10.100.235.94:8080/rs/ad/v1/6',
		//resCheckFuzzyQueryUrl : 'http://10.100.235.94:8080/rs/ad/v1/7',
		//mobileQueryItemUrl : 'http://10.100.235.94:8080/rs/ad/v1/8',
		//mobileQueryUrl : 'http://10.100.235.94:8080/rs/ad/v1/9',
		//mobilePublishImgQueryUrl : 'http://10.100.235.94:8080/rs/ad/v1/10',
		//mobileCheckDetailUrl : 'http://10.100.235.94:8080/rs/ad/v1/11',
		//saveCheckResultUrl : 'http://10.100.235.94:8080/rs/ad/v1/12',
		//uploadExAppUrl : 'http://10.100.235.94:8080/rs/ad/v1/f/13'



		//settingUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/2',
		//codesUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/3',
		//queryNameUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/4',
		//queryUserUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/5',
		//queryBusOrStopUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/6',
		//resCheckFuzzyQueryUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/7',
		//mobileQueryItemUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/8',
		//mobileQueryUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/9',
		//mobilePublishImgQueryUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/10',
		//mobileCheckDetailUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/11',
		//saveCheckResultUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/12',
		//uploadExAppUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/f/13',
		//gpsUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/14',
		//checkTaskImgsUrl : 'http://jwebapi.wuhanbus.com:8125/rs/ad/v1/15'


		settingUrl : 'http://10.100.235.64:8060/gjad/system/setting.do',
		codesUrl : 'http://10.100.235.64:8060/gjad/system/codes.do',
		queryNameUrl : 'http://10.100.235.64:8060/gjad/user/queryName.do',
		queryUserUrl : 'http://10.100.235.64:8060/gjad/mobile/queryUser.do',
		queryBusOrStopUrl : 'http://10.100.235.64:8060/gjad/web/queryBusOrStop.do',
		resCheckFuzzyQueryUrl : 'http://10.100.235.64:8060/gjad/web/resCheckFuzzyQuery.do',
		mobileQueryItemUrl : 'http://10.100.235.64:8060/gjad/checkTask/mobileQueryItem.do',
		mobileQueryUrl : 'http://10.100.235.64:8060/gjad/checkTask/mobileQuery.do',
		mobilePublishImgQueryUrl : 'http://10.100.235.64:8060/gjad/checkTask/mobilePublishImgQuery.do',
		mobileCheckDetailUrl : 'http://10.100.235.64:8060/gjad/checkTask/mobileCheckDetail.do',
		saveCheckResultUrl : 'http://10.100.235.64:8060/gjad/checkTask/saveCheckResult.do',
		uploadExAppUrl : 'http://10.100.235.64:8060/gjad/file/uploadEx.do',
		gpsUrl : 'http://10.100.235.64:8060/gjad/media/bus/gps.do',
		checkTaskImgsUrl : 'http://10.100.235.64:8060/gjad/checkTask/checkTaskImgs.do'


	})

	.factory('settings', ['$rootScope', 'Page', function($rootScope, Page) {
		var settings = {};

		var __local = window.location;
		var __contextPath = __local.pathname.split("/")[1];
		var __basePath = __local.protocol+"//"+__local.host+"/"+__contextPath;
		settings.basePath = __basePath;
		$rootScope.settings = settings;
		return settings;
	}])

	.factory('localStore',['$window',function($window){
		return{        //存储单个属性
			set :function(key,value){
				$window.localStorage[key]=value;
			},        //读取单个属性
			get:function(key,defaultValue){
				return  $window.localStorage[key] || defaultValue;
			},        //存储对象，以JSON格式存储
			setObject:function(key,value){
				$window.localStorage[key]=JSON.stringify(value);
			},        //读取对象
			getObject: function (key) {
				return JSON.parse($window.localStorage[key] || '{}');
			}
		}
	}])
	.factory('sessionStore',['$window',function($window){
		return{        //存储单个属性
			set :function(key,value){
				$window.sessionStorage[key]=value;
			},        //读取单个属性
			get:function(key,defaultValue){
				return  $window.sessionStorage[key] || defaultValue;
			},        //存储对象，以JSON格式存储
			setObject:function(key,value){
				$window.sessionStorage[key]=JSON.stringify(value);
			},        //读取对象
			getObject: function (key) {
				return JSON.parse($window.sessionStorage[key] || '{}');
			}
		}
	}])

	.factory('HttpInterceptor', function () {
		// ---
		// PRVIATE METHODS.
		// ---
		// I serialize the given Object into a key-value pair string. This
		// method expects an object and will default to the toString() method.
		// --
		// NOTE: This is an atered version of the jQuery.param() method which
		// will serialize a data collection for Form posting.
		// --
		// https://github.com/jquery/jquery/blob/master/src/serialize.js#L45
		function serializeData(data) {
			// If this is not an object, defer to native stringification.
			if (!angular.isObject(data)) {
				return ((data == null) ? "" : data.toString());
			}
			var buffer = [];
			// Serialize each key in the object.
			for (var name in data) {
				if (!data.hasOwnProperty(name)) {
					continue;
				}
				var value = data[name];
				if (angular.isObject(value)) {
					value = angular.toJson(value);
				}
				buffer.push(encodeURIComponent(name) + "=" + encodeURIComponent((value == null) ? "" : value));
			}
			// Serialize the buffer and clean it up for transportation.
			var source = buffer.join("&").replace(/%20/g, "+");
			return (source);
		}

		return {
			request: function (config) {
				if (config.data && angular.isObject(config.data)) {
					if (config.method === 'POST') {
						config.data = serializeData(config.data);
					} else if (config.method === 'GET') {
						config.url += (config.url.indexOf('?') > 0 ? '&' : '?') + serializeData(config.data);
					}
				}

				return config;
			}
		};
	})

	.service('Page', function($rootScope, $http, $state, ApiEndpoint,$ionicPopup,$ionicLoading,$timeout,localStore) { // injectables go here
		var self = this; // Save reference

		this.alert = function(message, yesCallback) {
//		layer.open({
//			content : message,
//			btn : ['OK'],
//			yes : function(index) {
//				if (yesCallback) {
//					layer.close(index)
//					yesCallback();
//				}
//			}
//		});

			var alertPopup = $ionicPopup.alert({
				cssClass : 'popup_alert',
				template: message,
				okText:'OK',
				okType:'button-clear button-positive'
			});
			alertPopup.then(function(res) {
				if (yesCallback) {
					yesCallback();
				}
			});

		};

		this.notice = function(message,callback) {
//		layer.open({
//			content : message,
//			time : 2
//		});

			var noticePopup = $ionicPopup.alert({
				cssClass : 'popup_notice',
				template: message,
				buttons:null
			});
			noticePopup.then(function(res) {
				if (callback) {
					callback();
				}
			});
			$timeout(function() {
				noticePopup.close();
			}, 1500);
		};

		this.confirm = function(message, yesCallback, cancelCallback) {
//		layer.open({
//			content : message,
//			btn : ['确认', '取消'],
//			shadeClose : false,
//			anim : false,
//			yes : function(index) {
//				if (yesCallback) {
//					layer.close(index)
//					yesCallback();
//				}
//			},
//			no : function() {
//			}
//		});

			var confirmPopup = $ionicPopup.confirm({
				cssClass : 'popup_confirm',
				template: message,
				cancelText: '取消',
				cancelType: 'button-clear button-positive',
				okText: '确认',
				okType: 'button-clear button-positive'
			}).then(function(res) {
				if(res) {
					if (yesCallback) {
						yesCallback();
					}
				} else {
					if (cancelCallback) {
						cancelCallback();
					}
				}
			});
		};

		this.ajax = function(method, url, data, isFilter, callback, errorCallback) {

			var loadi = null;
			//取消layer弹框，改为ionic弹框
			if (isFilter) {
//			loadi = layer.open({
//				type : 2,
//				content : ''
//			});
				loadi = $ionicLoading.show({
					template: '<ion-spinner icon="ios-small"></ion-spinner>'
					//duration: 15000
				});
			}

			data = data || {};
			//data["access_token"] = localStore.get("token");
			//data["userId"] = localStore.get("userId");
			//if(url.indexOf("http://10.100.235.94:8080/rs/ad") != -1) {
			//	data["url"] = url;
			//	url = "web/changeOAuth.do";
			//}
			$http({
				method : method,
				//url :  ApiEndpoint.url + url,
				url :  url,
				data : data,
				cache : false
			}).success(function(response) {
				if (loadi != null) {
					//layer.close(loadi);
					$ionicLoading.hide();
				}
				if (response.resultCode == '1' || url.indexOf('service/') == 0) { //成功
					if (callback) {
						callback(response);
					}
				} else if (errorCallback) {
					errorCallback(response)
				} else if (response.resultCode) {
					self.notice(response.resultDes);
				}
			});
		};

		this.ajaxPost = function(url, data, callback, errorCallback) {
			this.ajax('POST', url, data, true, callback, errorCallback);
		};

		this.ajaxPostQuiet = function(url, data, callback, errorCallback) {
			this.ajax('POST', url, data, false, callback, errorCallback);
		};

		this.ajaxGet = function(url, data, callback, errorCallback) {
			this.ajax('GET', url, data, true, callback, errorCallback);
		};

		this.ajaxGetQuiet = function(url, data, callback, errorCallback) {
			this.ajax('GET', url, data, false, callback, errorCallback);
		};

		this.ajaxPut = function(url, data, callback, errorCallback) {
			if (!data) {
				data = {};
			}
			data._method = 'PUT';
			this.ajaxPost(url, data, callback, errorCallback);
		},

			this.ajaxDelete = function(url, data, callback, errorCallback) {
				if (!data) {
					data = {};
				}
				data._method = 'DELETE';
				this.ajaxPost(url, data, callback, errorCallback);
			}

	})
	.filter('to_trusted', ['$sce', function($sce) {
		return function(text) {
			return $sce.trustAsHtml(text);
		};
	}])

	.service('XCode', function($rootScope, Page,ApiEndpoint) {

		this.init = function() {
			Page.ajaxPost(ApiEndpoint.codesUrl, null, function(response) {
				$rootScope.options = response.data;
			});
		}

		this.queryCodes = function(url, param, callback) {
			Page.ajaxPost(url, param, function(response) {
				var code = url;
				if (param) {
					code += angular.toJson(param);
				}
				$rootScope.options[code] = response.data;
				if (callback) {
					callback(response.data);
				}
			});
		}

		this.queryUsers = function(ids, callback) {
			if (ids && ids.length > 0) {
				var users = [], userOption = $rootScope.options['user'] || {};
				$(ids).each(function(index, id) {
					if (!userOption[id]) {
						users.push(id);
					}
				});
				if (users.length > 0) {
					Page.ajaxPost(ApiEndpoint.queryNameUrl, {
						ids : users.join(',')
					}, function(response) {
						$(response.data).each(function(index, user) {
							userOption[user.userId] = user.userName;
						});
						$rootScope.options['user'] = userOption;
						callback();
					});
				} else {
					callback();
				}
			} else {
				callback();
			}
		}

		this.getName = function(codeType, value) {
			var name = value;
			if (codeType == 'user') {// 用户
				name = $rootScope.options[codeType][value] || value;
			} else {
				$($rootScope.options[codeType]).each(function(index, option) {
					if (option.value == value) {
						name = option.name;
						return false;// break
					}
				});
			}
			return name;
		};

		this.getSelectOption = function(codeType) {
			var options = $rootScope.options[codeType];
			if (!options) {
				options = [];
			}
			return options;
		}
	});

var AppUtil = function () {
	return {

		// 获取model的小数点最后部分
		getModelName: function(modelName) {
			if (modelName.indexOf('.') > 0) {
				modelName = modelName.substring(modelName.lastIndexOf('.') + 1, modelName.length);
			}
			return modelName;
		},

		// 获取model的小数点最后部分
		getModelValue: function(scope, modelName) {
			if (modelName.indexOf('.') > 0) {
				var arr = modelName.split('.');
				var value = scope;
				$(arr).each(function(ii, modelName2) {
					if (angular.isUndefined(value)) {
						value = null;
						return false;
					} else {
						value = value[modelName2];
					}
				});
				return value;
			} else {
				return scope[modelName];
			}
		},

		jsonfy: function(json) {
			//return jsonfy('{' + (json || '') + '}');
			return eval('[{' + (json || '') + '}]')[0];
		},

		GPS : {
			PI : 3.14159265358979324,
			x_pi : 3.14159265358979324 * 3000.0 / 180.0,
			delta : function (lat, lon) {
				// Krasovsky 1940
				//
				// a = 6378245.0, 1/f = 298.3
				// b = a * (1 - f)
				// ee = (a^2 - b^2) / a^2;
				var a = 6378245.0; //  a: 卫星椭球坐标投影到平面地图坐标系的投影因子。
				var ee = 0.00669342162296594323; //  ee: 椭球的偏心率。
				var dLat = this.transformLat(lon - 105.0, lat - 35.0);
				var dLon = this.transformLon(lon - 105.0, lat - 35.0);
				var radLat = lat / 180.0 * this.PI;
				var magic = Math.sin(radLat);
				magic = 1 - ee * magic * magic;
				var sqrtMagic = Math.sqrt(magic);
				dLat = (dLat * 180.0) / ((a * (1 - ee)) / (magic * sqrtMagic) * this.PI);
				dLon = (dLon * 180.0) / (a / sqrtMagic * Math.cos(radLat) * this.PI);
				return {'lat': dLat, 'lon': dLon};
			},

			//WGS-84 to GCJ-02
			gcj_encrypt : function (wgsLat, wgsLon) {
				if (this.outOfChina(wgsLat, wgsLon))
					return {'lat': wgsLat, 'lon': wgsLon};

				var d = this.delta(wgsLat, wgsLon);
				return {'lat' : wgsLat + d.lat,'lon' : wgsLon + d.lon};
			},
			//GCJ-02 to WGS-84
			gcj_decrypt : function (gcjLat, gcjLon) {
				if (this.outOfChina(gcjLat, gcjLon))
					return {'lat': gcjLat, 'lon': gcjLon};

				var d = this.delta(gcjLat, gcjLon);
				return {'lat': gcjLat - d.lat, 'lon': gcjLon - d.lon};
			},
			//GCJ-02 to WGS-84 exactly
			gcj_decrypt_exact : function (gcjLat, gcjLon) {
				var initDelta = 0.01;
				var threshold = 0.000000001;
				var dLat = initDelta, dLon = initDelta;
				var mLat = gcjLat - dLat, mLon = gcjLon - dLon;
				var pLat = gcjLat + dLat, pLon = gcjLon + dLon;
				var wgsLat, wgsLon, i = 0;
				while (1) {
					wgsLat = (mLat + pLat) / 2;
					wgsLon = (mLon + pLon) / 2;
					var tmp = this.gcj_encrypt(wgsLat, wgsLon)
					dLat = tmp.lat - gcjLat;
					dLon = tmp.lon - gcjLon;
					if ((Math.abs(dLat) < threshold) && (Math.abs(dLon) < threshold))
						break;

					if (dLat > 0) pLat = wgsLat; else mLat = wgsLat;
					if (dLon > 0) pLon = wgsLon; else mLon = wgsLon;

					if (++i > 10000) break;
				}
				//console.log(i);
				return {'lat': wgsLat, 'lon': wgsLon};
			},
			//GCJ-02 to BD-09
			bd_encrypt : function (gcjLat, gcjLon) {
				var x = gcjLon, y = gcjLat;
				var z = Math.sqrt(x * x + y * y) + 0.00002 * Math.sin(y * this.x_pi);
				var theta = Math.atan2(y, x) + 0.000003 * Math.cos(x * this.x_pi);
				var bdLon = z * Math.cos(theta) + 0.0065;
				var bdLat = z * Math.sin(theta) + 0.006;
				return {'lat' : bdLat,'lon' : bdLon};
			},
			//BD-09 to GCJ-02
			bd_decrypt : function (bdLat, bdLon) {
				var x = bdLon - 0.0065, y = bdLat - 0.006;
				var z = Math.sqrt(x * x + y * y) - 0.00002 * Math.sin(y * this.x_pi);
				var theta = Math.atan2(y, x) - 0.000003 * Math.cos(x * this.x_pi);
				var gcjLon = z * Math.cos(theta);
				var gcjLat = z * Math.sin(theta);
				return {'lat' : gcjLat, 'lon' : gcjLon};
			},
			//WGS-84 to Web mercator
			//mercatorLat -> y mercatorLon -> x
			mercator_encrypt : function(wgsLat, wgsLon) {
				var x = wgsLon * 20037508.34 / 180.;
				var y = Math.log(Math.tan((90. + wgsLat) * this.PI / 360.)) / (this.PI / 180.);
				y = y * 20037508.34 / 180.;
				return {'lat' : y, 'lon' : x};
				/*
				 if ((Math.abs(wgsLon) > 180 || Math.abs(wgsLat) > 90))
				 return null;
				 var x = 6378137.0 * wgsLon * 0.017453292519943295;
				 var a = wgsLat * 0.017453292519943295;
				 var y = 3189068.5 * Math.log((1.0 + Math.sin(a)) / (1.0 - Math.sin(a)));
				 return {'lat' : y, 'lon' : x};
				 //*/
			},
			// Web mercator to WGS-84
			// mercatorLat -> y mercatorLon -> x
			mercator_decrypt : function(mercatorLat, mercatorLon) {
				var x = mercatorLon / 20037508.34 * 180.;
				var y = mercatorLat / 20037508.34 * 180.;
				y = 180 / this.PI * (2 * Math.atan(Math.exp(y * this.PI / 180.)) - this.PI / 2);
				return {'lat' : y, 'lon' : x};
				/*
				 if (Math.abs(mercatorLon) < 180 && Math.abs(mercatorLat) < 90)
				 return null;
				 if ((Math.abs(mercatorLon) > 20037508.3427892) || (Math.abs(mercatorLat) > 20037508.3427892))
				 return null;
				 var a = mercatorLon / 6378137.0 * 57.295779513082323;
				 var x = a - (Math.floor(((a + 180.0) / 360.0)) * 360.0);
				 var y = (1.5707963267948966 - (2.0 * Math.atan(Math.exp((-1.0 * mercatorLat) / 6378137.0)))) * 57.295779513082323;
				 return {'lat' : y, 'lon' : x};
				 //*/
			},
			// two point's distance
			distance : function (latA, lonA, latB, lonB) {
				var earthR = 6371000.;
				var x = Math.cos(latA * this.PI / 180.) * Math.cos(latB * this.PI / 180.) * Math.cos((lonA - lonB) * this.PI / 180);
				var y = Math.sin(latA * this.PI / 180.) * Math.sin(latB * this.PI / 180.);
				var s = x + y;
				if (s > 1) s = 1;
				if (s < -1) s = -1;
				var alpha = Math.acos(s);
				var distance = alpha * earthR;
				return distance;
			},
			outOfChina : function (lat, lon) {
				if (lon < 72.004 || lon > 137.8347)
					return true;
				if (lat < 0.8293 || lat > 55.8271)
					return true;
				return false;
			},
			transformLat : function (x, y) {
				var ret = -100.0 + 2.0 * x + 3.0 * y + 0.2 * y * y + 0.1 * x * y + 0.2 * Math.sqrt(Math.abs(x));
				ret += (20.0 * Math.sin(6.0 * x * this.PI) + 20.0 * Math.sin(2.0 * x * this.PI)) * 2.0 / 3.0;
				ret += (20.0 * Math.sin(y * this.PI) + 40.0 * Math.sin(y / 3.0 * this.PI)) * 2.0 / 3.0;
				ret += (160.0 * Math.sin(y / 12.0 * this.PI) + 320 * Math.sin(y * this.PI / 30.0)) * 2.0 / 3.0;
				return ret;
			},
			transformLon : function (x, y) {
				var ret = 300.0 + x + 2.0 * y + 0.1 * x * x + 0.1 * x * y + 0.1 * Math.sqrt(Math.abs(x));
				ret += (20.0 * Math.sin(6.0 * x * this.PI) + 20.0 * Math.sin(2.0 * x * this.PI)) * 2.0 / 3.0;
				ret += (20.0 * Math.sin(x * this.PI) + 40.0 * Math.sin(x / 3.0 * this.PI)) * 2.0 / 3.0;
				ret += (150.0 * Math.sin(x / 12.0 * this.PI) + 300.0 * Math.sin(x / 30.0 * this.PI)) * 2.0 / 3.0;
				return ret;
			}
		}
	}
}();
